package com.blackoreo.monitor;

import com.blackoreo.monitor.cache.BlackOreoCache;
import com.blackoreo.monitor.conf.BlackOreoConf;
import com.blackoreo.monitor.entry.BlackOreoEntryGroup;
import com.blackoreo.monitor.func.ExceptionFunc;
import com.blackoreo.monitor.servlet.MonitorServlet;
import org.eclipse.jetty.server.Server;
import org.eclipse.jetty.servlet.ServletContextHandler;

/**
 * PackageName: com.blackoreo.monitor
 * Author: txw
 * Date: 2021/4/8
 * Description: Monitor server.
 */
public class BlackOreoMonitor {

    protected Server server;

    public static BlackOreoMonitor startMonitor(String appName, String appDesc, int port, ExceptionFunc handler) {
        BlackOreoCache.setExceptionFunc(handler);
        return startMonitor(appName, appDesc, port);
    }

    public static BlackOreoMonitor startMonitor(String appName, String appDesc, int port ) {
        System.setProperty(BlackOreoConf.PORT.getPropertiesName(), port + "");
        return startMonitor(appName, appDesc);
    }

    public static BlackOreoMonitor startMonitor(String appName, String appDesc) {
        BlackOreoMonitor blackOreoMonitor = new BlackOreoMonitor();
        blackOreoMonitor.server = new Server(getPort());
        ServletContextHandler servletHandler = new ServletContextHandler();
        servletHandler.addServlet(MonitorServlet.class
                , BlackOreoConf.PATH.getValue().toString());
        blackOreoMonitor.server.setHandler(servletHandler);
        try {
            Thread daemonListener = new Thread(() -> {
                try {
                    blackOreoMonitor.server.start();
                } catch (Exception exception) {
                    exception.printStackTrace();
                }
            });
            daemonListener.setDaemon(true);
            daemonListener.setName(BlackOreoConf.THREAD_NAME.getValue().toString());
            daemonListener.start();
        } catch (Exception exception) {
            exception.printStackTrace();
            BlackOreoCache.handle(exception);
        }
        BlackOreoCache.init(appName, appDesc);
        return blackOreoMonitor;
    }

    /**
     * Registry a group to Monitor Server.
     * @param groupName {@link String} group name.
     * @param groupDesc {@link String} group description.
     * @return {@link BlackOreoEntryGroup}
     */
    public BlackOreoEntryGroup group(String groupName, String groupDesc) {
        return new BlackOreoEntryGroup(groupName, groupDesc);
    }

    public static int getPort() {
        return (int)BlackOreoConf.PORT.getValue();
    }
}
